from sqlalchemy.ext.asyncio import AsyncSession
from fastapi import HTTPException, status

from app.core import security
from app.db.models.user import User
from app.schemas.user import UserCreate
from app.services import user as user_service
from app.services import notification # Import notification service

async def register_new_user(db: AsyncSession, user_in: UserCreate) -> User:
    """Creates a new user in the database and sends verification email."""
    # Check if username or email already exists
    existing_user = await user_service.get_user_by_username(db, user_in.username)
    if existing_user:
        raise HTTPException(
            status_code=status.HTTP_400_BAD_REQUEST,
            detail="Username already registered",
        )
    existing_email = await user_service.get_user_by_email(db, user_in.email)
    if existing_email:
        raise HTTPException(
            status_code=status.HTTP_400_BAD_REQUEST,
            detail="Email already registered",
        )

    hashed_password = security.get_password_hash(user_in.password)
    db_user = User(
        username=user_in.username,
        email=user_in.email,
        password_hash=hashed_password,
        is_active=False # Start as inactive until email verification
    )
    db.add(db_user)
    await db.commit()
    await db.refresh(db_user)
    # Send verification email
    try:
        await notification.send_verification_email(db_user)
    except Exception as e:
        # Log error but don't fail registration if email sending fails
        # User can potentially request verification email again later
        # Or admin can manually activate
        import logging # Temporary import
        logging.exception(f"Failed to send verification email to {db_user.email}")
    return db_user

async def authenticate_user(
    db: AsyncSession, username: str, password: str
) -> User | None:
    """Authenticates a user by username and password."""
    user = await user_service.get_user_by_username(db, username)
    if not user:
        return None
    if not security.verify_password(password, user.password_hash):
        return None
    # Optional: Check if user is active (email verified)
    # if not user.is_active:
    #     raise HTTPException(status_code=400, detail="Inactive user. Please verify your email.")
    return user

# We might need a separate user_service.py for CRUD operations later
# For now, keeping get_user_by_username/email here for auth context
